package com.pricy.me.model;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.UnsupportedEncodingException;
import java.lang.reflect.Type;
import java.net.UnknownHostException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.ArrayList;
import java.util.List;

import org.apache.http.HttpResponse;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.conn.HttpHostConnectException;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.util.EntityUtils;

import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.Environment;
import android.util.Log;
import android.widget.Toast;

import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonArray;
import com.google.gson.JsonParser;
import com.google.gson.reflect.TypeToken;
import com.pricy.me.R;

public class Product{
	protected int id;
    protected boolean owner;
	protected String title;
    protected double price;
    protected String currency;
    protected String by;
    protected String adress;
    protected double latitude;
    protected double longitude;
    protected String description;
    protected String photo;
    protected int quality = 0;
    protected int visiblity = 0;
    protected int views = 0;
    protected Category category;
    protected User user;
    protected Date date;
    public static int USER_PRODUCTS = 0;
    public static int BONNE_AFFAIRE = 1;
    public static int JE_LAI = 2;
    

	public String toJSON(){
		Gson gson = new Gson();
		return gson.toJson(this);
	}
    
    public void addProduct(Context c, Product p){
    	Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd'T'HH:mm:ssZ").create();
    	String jsonOutput = readFile("products.info", c);
    	Type listType = new TypeToken<List<Product>>(){}.getType();
    	if(jsonOutput.length() < 2){
    		ArrayList<Product> empty = new ArrayList<Product>();
    		jsonOutput = gson.toJson(empty);
    	}
    	
    	@SuppressWarnings("unchecked")
		List<Product> products = (List<Product>) gson.fromJson(jsonOutput, listType);
    	products.add(p);
    	String jsonInput = gson.toJson(products);
    	writeFile("products.info", jsonInput, c);
    }
    
    
	@SuppressWarnings("unchecked")
	public List<ProductExtended> getLocalProducts(Context c){
    	Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd'T'HH:mm:ssZ").create();
    	String jsonOutput = readFile("products.info", c);
    	
    	List<ProductExtended> products = new ArrayList<ProductExtended>();
    	if(jsonOutput.length() < 2){
    		return products;
    	}
    	
    	Type listType = new TypeToken<ArrayList<ProductExtended>>(){}.getType();
    	products = (ArrayList<ProductExtended>) gson.fromJson(jsonOutput, listType);
		return products;
    }
	
	@SuppressWarnings("unchecked")
	public List<ProductExtended> getLastProducts(Context c) {
        	
		List<ProductExtended> products = new ArrayList<ProductExtended>();
		Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd'T'HH:mm:ssZ").create();
		String jsonOutput = readFile("stream.info", c);
		final String productStreamUser= c.getResources().getString(R.string.lien)+"api/product/stream?user=" ;
		Type listType = new TypeToken<ArrayList<ProductExtended>>(){}.getType();
		try {
			// Create a new HttpClient and Post Header
	        HttpClient httpclient = new DefaultHttpClient();
	        HttpPost httppost = null;
	     // Execute HTTP Post Request
            HttpResponse response = null;
            String reponse = null;
			
			User user = new User();
			user.loadData(c);
			
	    	if(jsonOutput.length() < 5){
	    		// user&new
	    		
	    		 httppost = new HttpPost(productStreamUser+user.getId()+"&last=new");
	    		 response = httpclient.execute(httppost);
	 	    	 reponse = EntityUtils.toString(response.getEntity());
	 	    	JsonParser parser = new JsonParser();
	 	        JsonArray array = parser.parse(reponse).getAsJsonArray();
	 	       products = (ArrayList<ProductExtended>) gson.fromJson(reponse, listType);
	 	        for (int i = 0; i < array.size(); i++) {
	 	        	User u = gson.fromJson(array.get(i).getAsJsonObject().get("user"), User.class);
	 	        	products.get(i).setUser(u);
	 	        	Category cat = gson.fromJson(array.get(i).getAsJsonObject().get("category"), Category.class);
	 	        	products.get(i).setCategory(cat);
				}
		    	writeFile("stream.info", reponse, c);
		    	//if(products.size()>0){
		    	 writeFile("laststream.info", ""+products.get(0).getId(), c);
		    	//}
		    	return products;
		    	
	    	}
	    	else{
	    		// user&last
	    		httppost = new HttpPost(productStreamUser+user.getId()+"&last="+readFile("laststream.info", c));
	    		response = httpclient.execute(httppost);
		    	reponse = EntityUtils.toString(response.getEntity());
		    	Log.e("URL", productStreamUser+user.getId()+"&last="+readFile("laststream.info", c));
	    		if(reponse.equals("uptodate")){
		    		products = new ArrayList<ProductExtended>();
		    		JsonParser parser = new JsonParser();
		 	        JsonArray array = parser.parse(jsonOutput).getAsJsonArray();
		 	       products = (ArrayList<ProductExtended>) gson.fromJson(jsonOutput, listType);
		 	        for (int i = 0; i < array.size(); i++) {
		 	        	User u = gson.fromJson(array.get(i).getAsJsonObject().get("user"), User.class);
		 	        	products.get(i).setUser(u);
		 	        	Category cat = gson.fromJson(array.get(i).getAsJsonObject().get("category"), Category.class);
		 	        	products.get(i).setCategory(cat);
					}
		        	return products;
	    		}
	    		if(!reponse.equals("error")){
	    			products = new ArrayList<ProductExtended>();
	    			JsonParser parser = new JsonParser();
		 	        JsonArray array = parser.parse(reponse).getAsJsonArray();
		 	       products = (ArrayList<ProductExtended>) gson.fromJson(reponse, listType);
		 	        for (int i = 0; i < array.size(); i++) {
		 	        	User u = gson.fromJson(array.get(i).getAsJsonObject().get("user"), User.class);
		 	        	products.get(i).setUser(u);
		 	        	Category cat = gson.fromJson(array.get(i).getAsJsonObject().get("category"), Category.class);
		 	        	products.get(i).setCategory(cat);
					}
		        	writeFile("stream.info", reponse, c);
		        	writeFile("laststream.info", ""+products.get(0).getId(), c);
		        	return products;
	    		}
	    	}

		} catch (UnsupportedEncodingException e) {
			Log.e("ERROR", e.toString());
		} catch (ClientProtocolException e) {
			Log.e("ERROR", e.toString());
		} catch (HttpHostConnectException e) {
			products = new ArrayList<ProductExtended>();
        	products = (ArrayList<ProductExtended>) gson.fromJson(jsonOutput, listType);
        	return products;
		} catch (UnknownHostException e) {
			products = new ArrayList<ProductExtended>();
        	products = (ArrayList<ProductExtended>) gson.fromJson(jsonOutput, listType);
        	return products;
		} catch (IOException e) {
			Log.e("ERROR", e.toString());
		}
		
		return products;
    			
	}
	
	@SuppressWarnings("unchecked")
	public List<ProductExtended> getLoadProducts(Date date,Context c) {
		List<ProductExtended> products = new ArrayList<ProductExtended>();
		SimpleDateFormat sdf = new SimpleDateFormat();
		sdf.applyPattern("yyyy-MM-dd'T'HH:mm:ssZ");
		final String productStreamloadUser= c.getResources().getString(R.string.lien)+"api/product/streamload?user=" ;
		
		try {
			User user = new User();
			user.loadData(c);
			
			Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd'T'HH:mm:ssZ").create();
			// Create a new HttpClient and Post Header
	        HttpClient httpclient = new DefaultHttpClient();
	        Log.e("MORE",productStreamloadUser+user.getId()+"&date="+sdf.format(date));
			 HttpPost httppost = new HttpPost(productStreamloadUser+user.getId()+"&date="+sdf.format(date));
			 HttpResponse response = httpclient.execute(httppost);
			
			String reponse = EntityUtils.toString(response.getEntity());
	    	 Log.e("REPONSE", reponse);
	    	Type listType = new TypeToken<ArrayList<ProductExtended>>(){}.getType();
			JsonParser parser = new JsonParser();
	        JsonArray array = parser.parse(reponse).getAsJsonArray();
	        products = (ArrayList<ProductExtended>) gson.fromJson(reponse, listType);
	        for (int i = 0; i < array.size(); i++) {
	        	User u = gson.fromJson(array.get(i).getAsJsonObject().get("user"), User.class);
	        	products.get(i).setUser(u);
	        	Category cat = gson.fromJson(array.get(i).getAsJsonObject().get("category"), Category.class);
	        	products.get(i).setCategory(cat);
			}
	        return products;
		} catch (UnsupportedEncodingException e) {
			Log.e("ERROR", e.toString());
		} catch (ClientProtocolException e) {
			Log.e("ERROR", e.toString());
		} catch (UnknownHostException e) {
			Log.e("ERROR", e.toString());
		} catch (IOException e) {
			Log.e("ERROR", e.toString());
		}

		return products;
	}
	
	@SuppressWarnings("unchecked")
	public List<ProductExtended> getUserProducts(int type,int user,Context context) {
		List<ProductExtended> products = new ArrayList<ProductExtended>();
		
		try {
		//	final String productStreamloadUser= c.getResources().getString(R.string.lien)+"api/product/streamload?user=" ;
		String url = "";
			if(type == Product.USER_PRODUCTS) url = context.getResources().getString(R.string.lien)+"api/product/streamuser?id="+user;
			else if(type == Product.BONNE_AFFAIRE) url = context.getResources().getString(R.string.lien)+"api/product/streamuseraction?id="+user+"&action=0";
			else if(type == Product.JE_LAI) url = context.getResources().getString(R.string.lien)+"api/product/streamuseraction?id="+user+"&action=1";
			
			Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd'T'HH:mm:ssZ").create();
			// Create a new HttpClient and Post Header
	        HttpClient httpclient = new DefaultHttpClient();
	        
			 HttpPost httppost = new HttpPost(url);
			 HttpResponse response = httpclient.execute(httppost);
			
			String reponse = EntityUtils.toString(response.getEntity());
	    	 
	    	Type listType = new TypeToken<ArrayList<ProductExtended>>(){}.getType();
			JsonParser parser = new JsonParser();
	        JsonArray array = parser.parse(reponse).getAsJsonArray();
	        products = (ArrayList<ProductExtended>) gson.fromJson(reponse, listType);
	        for (int i = 0; i < array.size(); i++) {
	        	User u = gson.fromJson(array.get(i).getAsJsonObject().get("user"), User.class);
	        	products.get(i).setUser(u);
	        	Category cat = gson.fromJson(array.get(i).getAsJsonObject().get("category"), Category.class);
	        	products.get(i).setCategory(cat);
			}
	        return products;
		} catch (UnsupportedEncodingException e) {
			Log.e("ERROR", e.toString());
		} catch (ClientProtocolException e) {
			Log.e("ERROR", e.toString());
		} catch (UnknownHostException e) {
			Log.e("ERROR", e.toString());
		} catch (IOException e) {
			Log.e("ERROR", e.toString());
		}

		return products;
	}
	
	public ArrayList<String> getNbrUserAction(int user ,Context context) {
		ArrayList<String> numbers = new ArrayList<String>();
		try {
			String url = context.getResources().getString(R.string.lien)+"api/product/nbruseraction?id="+user;
			// Create a new HttpClient and Post Header
	        HttpClient httpclient = new DefaultHttpClient();
	        
			 HttpPost httppost = new HttpPost(url);
			 HttpResponse response = httpclient.execute(httppost);
			String reponse = EntityUtils.toString(response.getEntity());
			
			String[] tokens = reponse.split("_");
			numbers.add(tokens[0]);
			numbers.add(tokens[1]);
			Log.e("NUMBERS", ""+tokens[0]);
	        return numbers;
		} catch (UnsupportedEncodingException e) {
			Log.e("ERROR", e.toString());
		} catch (ClientProtocolException e) {
			Log.e("ERROR", e.toString());
		} catch (UnknownHostException e) {
			Log.e("ERROR", e.toString());
		} catch (IOException e) {
			Log.e("ERROR", e.toString());
		}
		return numbers;
	}
	
	@SuppressWarnings("unchecked")
	public List<ProductExtended> getDiscoverProducts(int current,
			int categ, Context context) {
		List<ProductExtended> products = new ArrayList<ProductExtended>();
		User user = new User();
		user.loadData(context);
		try {
			String url = context.getResources().getString(R.string.lien)+"api/product/streamdiscover?cat="+categ+"&offset="+current+"&user="+user.getId();
			Log.e("DISCOVER", url);
			Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd'T'HH:mm:ssZ").create();
			// Create a new HttpClient and Post Header
	        HttpClient httpclient = new DefaultHttpClient();
	        
			 HttpPost httppost = new HttpPost(url);
			 HttpResponse response = httpclient.execute(httppost);
			
			String reponse = EntityUtils.toString(response.getEntity());
	    	Type listType = new TypeToken<ArrayList<ProductExtended>>(){}.getType();
			JsonParser parser = new JsonParser();
	        JsonArray array = parser.parse(reponse).getAsJsonArray();
	        products = (ArrayList<ProductExtended>) gson.fromJson(reponse, listType);
	        for (int i = 0; i < array.size(); i++) {
	        	User u = gson.fromJson(array.get(i).getAsJsonObject().get("user"), User.class);
	        	products.get(i).setUser(u);
	        	Category cat = gson.fromJson(array.get(i).getAsJsonObject().get("category"), Category.class);
	        	products.get(i).setCategory(cat);
			}
	        return products;
		} catch (UnsupportedEncodingException e) {
			Log.e("ERROR", e.toString());
		} catch (ClientProtocolException e) {
			Log.e("ERROR", e.toString());
		} catch (UnknownHostException e) {
			Log.e("ERROR", e.toString());
		} catch (IOException e) {
			Log.e("ERROR", e.toString());
		}

		return products;
	}
    
    public Bitmap getThumbnail() {

    	File sdCardDirectory = Environment.getExternalStorageDirectory();
        File image = new File(sdCardDirectory, "product-"+this.id+".jpg");
        Bitmap thumbnail = BitmapFactory.decodeFile(image.getAbsolutePath());
    	return thumbnail;
    }
    
    protected void writeFile(String file, String text, Context c){
		FileOutputStream fos;
		try {
			fos = c.openFileOutput(file, Context.MODE_PRIVATE);
			fos.write(text.getBytes());
        	fos.close();
		} catch (FileNotFoundException e) {
			Toast.makeText(c, "ERROR: can't open file", Toast.LENGTH_SHORT).show();
		} catch (IOException e) {
			Toast.makeText(c, "ERROR: can't write file", Toast.LENGTH_SHORT).show();
		}	
	}
    
    protected String readFile(String file, Context c) {
		StringBuilder json = new StringBuilder();
		try {
			FileInputStream fis = c.openFileInput(file);
			BufferedReader r = new BufferedReader(new InputStreamReader(fis));
			String line;
			while ((line = r.readLine()) != null) {
			    json.append(line);
			}
			fis.close();
			return json.toString();
		} catch (FileNotFoundException e) {
			e.printStackTrace();
			return "0";
		} catch (IOException e) {
			e.printStackTrace();
			return "0";
		}
	}
    
    
	
	public int getId() {
		return id;
	}
	public void setId(int id) {
		this.id = id;
	}
	public boolean isOwner() {
		return owner;
	}
	public void setOwner(boolean owner) {
		this.owner = owner;
	}
	public String getTitle() {
		return title;
	}
	public void setTitle(String title) {
		this.title = title;
	}
	public double getPrice() {
		return price;
	}
	public void setPrice(double d) {
		this.price = d;
	}
	public String getCurrency() {
		if(currency.equals("EUR")) return "€";
		else if(currency.equals("USD")) return "$";
		else if(currency.equals("MAD")) return "DH";
		else return currency;
	}
	public void setCurrency(String currency) {
		this.currency = currency;
	}
	public String getBy() {
		return by;
	}
	public void setBy(String by) {
		this.by = by;
	}
	public String getAdress() {
		return adress;
	}
	public void setAdress(String adress) {
		this.adress = adress;
	}
	public double getLatitude() {
		return latitude;
	}
	public void setLatitude(double latitude) {
		this.latitude = latitude;
	}
	public double getLongitude() {
		return longitude;
	}
	public void setLongitude(double longitude) {
		this.longitude = longitude;
	}
	public String getDescription() {
		return description;
	}
	public void setDescription(String description) {
		this.description = description;
	}
	public String getPhoto() {
		return photo;
	}
	public void setPhoto(String photo) {
		this.photo = photo;
	}
	public int getQuality() {
		return quality;
	}
	public void setQuality(int quality) {
		this.quality = quality;
	}
	public int getVisiblity() {
		return visiblity;
	}
	public void setVisiblity(int visiblity) {
		this.visiblity = visiblity;
	}
	public int getViews() {
		return views;
	}
	public void setViews(int views) {
		this.views = views;
	}
	public Category getCategory() {
		return category;
	}
	public void setCategory(Category category) {
		this.category = category;
	}
	public User getUser() {
		return user;
	}
	public void setUser(User user) {
		this.user = user;
	}

	public Date getDate() {
		return date;
	}

	public void setDate(Date date) {
		this.date = date;
	}
	
	public void setNow() {
		this.date = new Date();
	}

	

	

	
    
    
}
